// 错误处理工具
import { ElMessage, ElMessageBox, ElNotification } from 'element-plus'

// 错误类型
export const ErrorTypes = {
  NETWORK: 'network',
  VALIDATION: 'validation',
  PERMISSION: 'permission',
  TIMEOUT: 'timeout',
  PARSE: 'parse',
  EXECUTION: 'execution',
  RECORDING: 'recording',
  UNKNOWN: 'unknown'
}

// 错误级别
export const ErrorLevels = {
  INFO: 'info',
  WARNING: 'warning',
  ERROR: 'error',
  CRITICAL: 'critical'
}

class ErrorHandler {
  constructor() {
    this.errorQueue = []
    this.maxRetries = 3
    this.retryDelay = 1000
  }

  // 处理错误的主方法
  handleError(error, options = {}) {
    const {
      type = ErrorTypes.UNKNOWN,
      level = ErrorLevels.ERROR,
      showMessage = true,
      showNotification = false,
      retryable = false,
      context = '',
      silent = false
    } = options

    // 规范化错误对象
    const normalizedError = this.normalizeError(error, type, level, context)
    
    // 记录错误
    this.logError(normalizedError)
    
    // 显示用户友好的消息
    if (!silent && showMessage) {
      this.showErrorMessage(normalizedError, showNotification)
    }
    
    // 处理重试逻辑
    if (retryable && options.retryFn) {
      this.handleRetry(normalizedError, options)
    }
    
    return normalizedError
  }

  // 规范化错误对象
  normalizeError(error, type, level, context) {
    let message = '未知错误'
    let code = 'UNKNOWN_ERROR'
    let originalError = error

    if (error instanceof Error) {
      message = error.message
      code = error.code || error.name
    } else if (typeof error === 'string') {
      message = error
    } else if (error && typeof error === 'object') {
      message = error.message || error.msg || JSON.stringify(error)
      code = error.code || error.status
    }

    return {
      id: this.generateErrorId(),
      message,
      code,
      type,
      level,
      context,
      timestamp: new Date().toISOString(),
      originalError,
      userMessage: this.getUserFriendlyMessage(message, type),
      stack: originalError?.stack
    }
  }

  // 获取用户友好的错误消息
  getUserFriendlyMessage(message, type) {
    const friendlyMessages = {
      [ErrorTypes.NETWORK]: '网络连接失败，请检查网络设置',
      [ErrorTypes.VALIDATION]: '输入数据不正确，请检查并重试',
      [ErrorTypes.PERMISSION]: '权限不足，无法执行此操作',
      [ErrorTypes.TIMEOUT]: '操作超时，请稍后重试',
      [ErrorTypes.PARSE]: '数据格式错误，请检查脚本格式',
      [ErrorTypes.EXECUTION]: '脚本执行失败，请检查步骤配置',
      [ErrorTypes.RECORDING]: '录制过程出现问题，请重新开始录制'
    }

    return friendlyMessages[type] || message
  }

  // 显示错误消息
  showErrorMessage(errorObj, useNotification = false) {
    const { level, userMessage, context } = errorObj
    
    const title = context ? `${context}: ${userMessage}` : userMessage
    
    if (useNotification) {
      ElNotification({
        title: this.getLevelTitle(level),
        message: userMessage,
        type: this.getElementType(level),
        duration: this.getDuration(level),
        position: 'top-right'
      })
    } else {
      const elementType = this.getElementType(level)
      
      if (level === ErrorLevels.CRITICAL) {
        ElMessageBox.alert(userMessage, '严重错误', {
          type: 'error',
          confirmButtonText: '确定'
        })
      } else {
        ElMessage({
          type: elementType,
          message: title,
          duration: this.getDuration(level),
          showClose: true
        })
      }
    }
  }

  // 处理重试逻辑
  async handleRetry(errorObj, options) {
    const { retryFn, maxRetries = this.maxRetries, retryDelay = this.retryDelay } = options
    
    for (let attempt = 1; attempt <= maxRetries; attempt++) {
      try {
        await new Promise(resolve => setTimeout(resolve, retryDelay * attempt))
        const result = await retryFn()
        
        ElMessage.success(`重试成功 (${attempt}/${maxRetries})`)
        return result
      } catch (retryError) {
        if (attempt === maxRetries) {
          this.handleError(retryError, {
            ...options,
            retryable: false,
            context: `重试失败 (${maxRetries}次)`
          })
        }
      }
    }
  }

  // 记录错误
  logError(errorObj) {
    console.error('ErrorHandler:', errorObj)
    
    // 添加到错误队列
    this.errorQueue.push(errorObj)
    
    // 限制队列大小
    if (this.errorQueue.length > 100) {
      this.errorQueue = this.errorQueue.slice(-100)
    }
    
    // TODO: 发送到错误监控服务
    this.sendToErrorService(errorObj)
  }

  // 发送错误到监控服务
  sendToErrorService(errorObj) {
    // 这里可以集成如 Sentry、LogRocket 等错误监控服务
    if (process.env.NODE_ENV === 'production') {
      // 发送到错误监控服务
      console.log('Sending error to monitoring service:', errorObj)
    }
  }

  // 获取错误级别对应的标题
  getLevelTitle(level) {
    const titles = {
      [ErrorLevels.INFO]: '提示',
      [ErrorLevels.WARNING]: '警告',
      [ErrorLevels.ERROR]: '错误',
      [ErrorLevels.CRITICAL]: '严重错误'
    }
    return titles[level] || '通知'
  }

  // 获取Element UI组件类型
  getElementType(level) {
    const types = {
      [ErrorLevels.INFO]: 'info',
      [ErrorLevels.WARNING]: 'warning',
      [ErrorLevels.ERROR]: 'error',
      [ErrorLevels.CRITICAL]: 'error'
    }
    return types[level] || 'error'
  }

  // 获取消息显示时长
  getDuration(level) {
    const durations = {
      [ErrorLevels.INFO]: 3000,
      [ErrorLevels.WARNING]: 4000,
      [ErrorLevels.ERROR]: 5000,
      [ErrorLevels.CRITICAL]: 0 // 不自动关闭
    }
    return durations[level] || 4000
  }

  // 生成错误ID
  generateErrorId() {
    return `error_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`
  }

  // 获取错误历史
  getErrorHistory() {
    return [...this.errorQueue]
  }

  // 清除错误历史
  clearErrorHistory() {
    this.errorQueue = []
  }

  // 导出错误报告
  exportErrorReport() {
    const report = {
      timestamp: new Date().toISOString(),
      totalErrors: this.errorQueue.length,
      errors: this.errorQueue,
      summary: this.generateErrorSummary()
    }
    
    const blob = new Blob([JSON.stringify(report, null, 2)], { type: 'application/json' })
    const url = URL.createObjectURL(blob)
    const a = document.createElement('a')
    a.href = url
    a.download = `error-report-${Date.now()}.json`
    a.click()
    URL.revokeObjectURL(url)
  }

  // 生成错误摘要
  generateErrorSummary() {
    const summary = {
      byType: {},
      byLevel: {},
      recent: this.errorQueue.slice(-10)
    }
    
    this.errorQueue.forEach(error => {
      summary.byType[error.type] = (summary.byType[error.type] || 0) + 1
      summary.byLevel[error.level] = (summary.byLevel[error.level] || 0) + 1
    })
    
    return summary
  }
}

// 创建单例实例
export const errorHandler = new ErrorHandler()

// 便捷方法
export const handleError = (error, options) => errorHandler.handleError(error, options)

export const handleNetworkError = (error, options = {}) => 
  errorHandler.handleError(error, { ...options, type: ErrorTypes.NETWORK })

export const handleValidationError = (error, options = {}) =>
  errorHandler.handleError(error, { ...options, type: ErrorTypes.VALIDATION })

export const handleParseError = (error, options = {}) =>
  errorHandler.handleError(error, { ...options, type: ErrorTypes.PARSE })

export const handleExecutionError = (error, options = {}) =>
  errorHandler.handleError(error, { ...options, type: ErrorTypes.EXECUTION })

export const handleRecordingError = (error, options = {}) =>
  errorHandler.handleError(error, { ...options, type: ErrorTypes.RECORDING })

// Vue 3 插件
export const ErrorHandlerPlugin = {
  install(app) {
    // 全局错误处理
    app.config.errorHandler = (error, instance, info) => {
      errorHandler.handleError(error, {
        type: ErrorTypes.UNKNOWN,
        level: ErrorLevels.ERROR,
        context: `Vue Error: ${info}`,
        showMessage: true
      })
    }
    
    // 提供给组件使用
    app.provide('errorHandler', errorHandler)
    app.config.globalProperties.$handleError = handleError
  }
}

export default errorHandler
